package band.wukong.practice.urule.ext.console.filter;

import band.wukong.practice.urule.ext.console.SessionConst;
import band.wukong.practice.urule.ext.console.URIConst;
import com.bstek.urule.console.User;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.BeansException;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;
import org.springframework.stereotype.Component;

import javax.servlet.*;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;

/**
 * @author wukong(wukonggg@139.com)
 */
@Component
public class SessionFilter implements Filter, ApplicationContextAware {

    private static final Logger logger = LoggerFactory.getLogger(SessionFilter.class);

    @Value("${urule.ext.sessionFilter.verify}")
    private boolean verify;


    @Override
    public void init(FilterConfig filterConfig) throws ServletException {
        if (!verify) {
            logger.warn("SessionFilter将不检查当前Request的权限，请勿在生产环境使用此方式！");
        }
    }

    @Override
    public void doFilter(ServletRequest req, ServletResponse resp, FilterChain chain) throws IOException, ServletException {
        logger.debug("run filter");
        if (verify) {
            justDoIt(req, resp, chain);
        } else {
            doNoting(req, resp, chain);
        }
    }

    private void doNoting(ServletRequest req, ServletResponse resp, FilterChain chain) throws IOException, ServletException {
        chain.doFilter(req, resp);
    }

    private void justDoIt(ServletRequest req, ServletResponse resp, FilterChain chain) throws IOException, ServletException {
        HttpServletRequest request = (HttpServletRequest) req;
        HttpServletResponse response = (HttpServletResponse) resp;

        Object o = request.getSession().getAttribute(SessionConst.SESSION_USER);

        if (needExluding(request, response, chain)) {
            chain.doFilter(req, resp);
            return;
        }

        if (null == o) {
            redirect2login(request, response);
            return;
        } else {
            User user = (User) o;
            if (!validateUser(user)) {
                redirect2login(request, response);
                return;
            }
        }
        chain.doFilter(req, resp);
    }

    private boolean needExluding(HttpServletRequest request, HttpServletResponse response, FilterChain chain) throws IOException, ServletException {
        String requestURL = request.getRequestURL().toString();
        String requestName = requestURL.substring(requestURL.lastIndexOf("/") + 1);

        logger.debug("requestURL = " + requestURL);
        logger.debug("requestName = " + requestName);

        return requestName.equals("login")
                || requestName.equals("login.html")
                || requestName.matches(".*\\.js$")
                || requestName.matches(".*\\.css$");
    }

    private void redirect2login(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        response.sendRedirect(request.getContextPath() + URIConst.LOGIN_URI);
    }

    private boolean validateUser(User user) {
        return false;
    }

    @Override
    public void destroy() {

    }

    @Override
    public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {

    }
}
